﻿
// ## 2022/12/11 # 铃 # 统合所有的回合初计算

namespace ai
{

	/// =========================================================================================

	const bool 调试模式 = false;

	const int KEY = pk::hash("ai");

	pk::list<pk::force @> force_list;

	array<pk::list<pk::building@>> base_near_baselist(据点_末);
	array<pk::list<pk::building@>> base_neibor_baselist(据点_末);

	array<int> base_score(据点_末, 0); // 据点分(用于分配资源)
	array<int> base_in_line_level(据点_末, 0); // 据点距离前线最小距离(前线层级)
	array<int> base_in_line_score(据点_末, 0); // 据点运输分(用于运输计算)
	array<int> base_statue(据点_末, 0); // 据点运输分(用于运输计算)
	array<int> marchable_troops(据点_末, 0); // 据点和周遭总兵力
	array<int> retained_troops(据点_末, 0); // 据点态势分析:支援城市自身留存兵力
	array<int> base_around_self_troops(据点_末, 0); // 据点态势分析:据点周围友军兵力
	array<int> base_around_enemy_troops(据点_末, 0); // 据点态势分析:据点周围敌方兵力
	array<int> base_in_range_enemy_troops(据点_末, 0); // 据点态势分析:据点所属范围内敌方兵力
	array<int> base_in_range_enemy_troops_from_player(据点_末, 0); // 据点态势分析:据点所属范围内敌方兵力(来自玩家)
	array<int> base_max_effective_troops(据点_末, 0); // 据点态势分析:据点实际可用兵力
	array<int> base_atk_power(据点_末, 0); // 据点态势分析:据点进攻能力
	array<int> base_def_power(据点_末, 0); // 据点态势分析:据点防御能力
	array<int> base_attacked_troops(据点_末, 0); // 据点态势分析:正在攻击据点的部队
	array<int> base_attacking_troops(据点_末, 0); // 据点态势分析:据点出征的部队

	array<int> base_real_person(据点_末, 0); // 据点态势分析:城市实际武将数
	array<int> base_want_person(据点_末, 0); // 据点态势分析:城市合意武将数
	array<int> base_real_person_for_district(据点_末, 0); // 军团计算
	array<int> base_want_person_for_district(据点_末, 0); // 军团计算

	array<int> force_score(势力_末, 0); // 势力总的前线分(用于计算物资和人员分配)
	array<int> force_gold(势力_末, 0); // 势力金		//由于 ch::get_force_gold计算太慢,因此做全局统计存起来
	array<int> force_food(势力_末, 0); // 势力粮
	array<int> force_troops(势力_末, 0); // 势力兵
	array<int> force_troops_for_base(势力_末, 0); // 势力兵(仅限据点,用于据点兵分配)

	array<int> district_score(军团_末, 0); // 军团总的前线分(用于计算物资和人员分配)
	array<int> district_gold(军团_末, 0); // 军团金		
	array<int> district_food(军团_末, 0); // 军团粮
	array<int> district_troops(军团_末, 0); // 军团兵

	array<array<int>> force_attack_base_troops(势力_末, array<int>(据点_末, 0));  //某个势力正在攻击某个据点的兵力

	array<array<int>> base_attack_base_troops(据点_末, array<int>(据点_末, 0));  //某个据点正在攻击某个据点的兵力

	array<array<int>> force_to_force_enemy_base(势力_末, array<int>(势力_末, 0));  //某个势力和某个势力的敌对城市数量

	int base_id;

	class Main
	{
		pk::list<pk::person @> actors;

		Main()
		{
			pk::bind2(107, pk::trigger107_t(on_new_day), 999);
			pk::bind2(102, pk::trigger102_t(on_load), 999);

		}

		void on_new_day()
		{
			clear_data();
			get_near_base();
			calc_score();
			calc_score_unit();
			print_score();
		}

		void on_load()
		{
			clear_data();
			if (pk::get_scenario().loaded)
			{
				get_near_base();
				calc_score();
				calc_score_unit();

				print_score();
			}
		}


		void clear_data()
		{
			//******************************************清空所有array*****************************************************
			for (int i = 0; i < 据点_末; i++)
			{
				base_score[i] = 0;
				base_in_line_score[i] = 0;
				marchable_troops[i] = 0;
				retained_troops[i] = 0;
				base_around_self_troops[i] = 0;
				base_around_enemy_troops[i] = 0;
				base_in_range_enemy_troops[i] = 0;
				base_in_range_enemy_troops_from_player[i] = 0;
				base_max_effective_troops[i] = 0;
				base_atk_power[i] = 0;
				base_def_power[i] = 0;
				base_attacked_troops[i] = 0;
				base_real_person[i] = 0;
				base_want_person[i] = 0;
				base_real_person_for_district[i] = 0;
				base_want_person_for_district[i] = 0;
				base_attacking_troops[i] = 0;
			}
			for (int i = 0; i < 势力_末; i++)
			{
				force_score[i] = 0;
				force_gold[i] = 0;
				force_food[i] = 0;
				force_troops[i] = 0;
				force_troops_for_base[i] = 0;
				for (int j = 0; j < 据点_末; j++)
				{
					force_attack_base_troops[i][j] = 0;

				}
				for (int t = 0; t < 势力_末; t++)
				{
					force_to_force_enemy_base[i][t] = 0;

				}

			}

			for (int i = 0; i < 军团_末; i++)
			{
				district_score[i] = 0;
				district_gold[i] = 0;
				district_food[i] = 0;
				district_troops[i] = 0;
			}

			for (int i = 0; i < 据点_末; i++)
			{
				if (!pk::is_valid_force_id(i)) continue;
				for (int j = 0; j < 据点_末; j++)
				{
					base_attack_base_troops[i][j] = 0;
				}
			}

		}
		//---------------------------------------------------------------------------------------
		//          全局计算.清空和赋值
		//---------------------------------------------------------------------------------------
		void calc_score()
		{

			//******************************************计算势力排名*****************************************************
			force_list.clear();
			force_list = pk::get_force_list();

			force_list.sort(function(a, b) {
				int stat_a = int(pk::get_city_count(a) + pk::get_troops(a) / 10000 + ch::get_base_list(a).count + pk::get_person_list(a, pk::mibun_flags(身份_君主, 身份_都督, 身份_太守, 身份_一般)).count / 5.0);
				int stat_b = int(pk::get_city_count(b) + pk::get_troops(b) / 10000 + ch::get_base_list(b).count + pk::get_person_list(b, pk::mibun_flags(身份_君主, 身份_都督, 身份_太守, 身份_一般)).count / 5.0);
				return (stat_a > stat_b);
			});


			//************************************************************************************************************
			//------------------------------------------------武将循环赋值----------------------------------------------
			//************************************************************************************************************
			for (int i = 0; i < 可用武将_末; i++)
			{
				pk::person @person = pk::get_person(i);
				if (pk::check_mibun(person, pk::mibun_flags(身份_都督, 身份_太守, 身份_一般)))
				{

					if (person.order == 武将任务_移动 and pk::is_valid_base_id(person.target[0]))
						base_real_person[person.target[0]]++;
					//pk::info("person.service" + person.service);
					else if (person.service > -1)
						base_real_person[person.service]++;
				}

			}

			//************************************************************************************************************
			//------------------------------------------------据点循环赋值----------------------------------------------
			//************************************************************************************************************

			//******************************************************计算城市状态*****************************************************
			for (int i = 0; i < 据点_末; i++)
			{
				pk::building @building = pk::get_building(i);

				int neibor_enemy_base_count_1 = ch::near_enemy_base_count(building).first;
				int neibor_enemy_base_count_2 = ch::near_enemy_base_count(building).second;

				if (pk::enemies_around(building)) base_statue[i] = 0;											//兵临城下
				else if (ai::base_in_range_enemy_troops[i] > 0) base_statue[i] = 1;					//战斗状态
				else if (neibor_enemy_base_count_1 >= 3)base_statue[i] = 2;										//危险前线状态
				else if (neibor_enemy_base_count_1 >= 1 and neibor_enemy_base_count_1 < 3)base_statue[i] = 3;   //普通前线状态
				else if (i < 城市_末 and ch::near_enemy_city_count(building).first >= 1) base_statue[i] = 3;		//城市1格内有敌人城市,虽然不相邻,但也是前线
				else if (neibor_enemy_base_count_1 == 0 and neibor_enemy_base_count_2 > 0)base_statue[i] = 4;   //警戒前线状态
				else if (neibor_enemy_base_count_2 == 0)base_statue[i] = 5;									//后方状态
			}


			//*****************************************计算城市可用作战兵力*****************************************************
			for (int i = 0; i < 据点_末; i++)
			{
				pk::building @building = pk::get_building(i);
				marchable_troops[i] = int(pk::get_max_marchable_troops(pk::get_building(i)));

				int effective_person_count = pk::get_idle_person_list(building).count;
				int effective_weapon = pk::get_weapon_amount(building, 1) + pk::get_weapon_amount(building, 2) + pk::get_weapon_amount(building, 3) + pk::get_weapon_amount(building, 4);
				base_max_effective_troops[i] = pk::min(building.troops, int(effective_weapon * 0.85), (effective_person_count) * 6000);
			}

				//******************************************计算城市周围作战兵力*****************************************************

			for (int i = 0; i < 据点_末; i++)
			{
				pk::building @building = pk::get_building(i);
				auto range = pk::range(building.get_pos(), 1, 5 + (building.facility == 设施_都市 ? 1 : 0));
				for (int r = 0; r < int(range.length); r++)
				{
					auto unit = pk::get_unit(range[r]);
					if (pk::is_alive(unit))
					{
						if (!pk::is_enemy(building, unit))

							base_around_self_troops[i] += unit.troops;
						else
							base_around_enemy_troops[i] += unit.troops;

					}
				}
			}



	   //******************************************计算城市的前线分*****************************************************
			for (int i = 0; i < 据点_末; i++)
			{
				pk::building @building = pk::get_building(i);

				//因子1:受到的敌人威胁程度,用兵力*距离*真实距离进行加权
				for (int j = 0; j < 据点_末; j++)
				{
					if (i == j) continue;
					pk::building @neighbor_building = pk::get_building(j);
					if (building.get_force_id() != neighbor_building.get_force_id())
					{
						int distance = 255;
						if (pk::is_valid_pos(neighbor_building.pos) and pk::is_valid_pos(building.pos))
						{
							distance = pk::get_city_distance(pk::get_city_id(neighbor_building.pos), pk::get_city_id(building.pos));
							if (distance <= 1)base_score[i] += 5;
							if (distance <= 1 and neighbor_building.is_player())base_score[i] += 50;
							if (pk::get_building_distance(i, j) == 1) base_score[i] += 5;
							base_score[i] += int((2.0 + marchable_troops[j] / 10000.0) * 20 / sqrt(unit_distance[i][j] + 1) / sqrt(distance + 1) / sqrt(pk::max(base_in_line_level[i], 2)));
						}
					}
				}

				//因子2:对于处于战斗状态的城市加权
				if (base_statue[i] == 据点_兵临) base_score[i] += 50;
				else if (base_statue[i] == 据点_战斗) base_score[i] += 50;
				else if (base_statue[i] == 据点_危险) base_score[i] += 35;
				else if (base_statue[i] == 据点_前线) base_score[i] += 30;
				else if (base_statue[i] == 据点_警戒) base_score[i] /= 2;
				else if (base_statue[i] == 据点_后方) base_score[i] /= 3;

				//因子3:有空地的城市加权(早期大城需要人+中期攻下的新的据点 两种情况)
				int 空地数量 = 0;
				if (i < 建筑_城市末)
				{
					pk::city @city = pk::building_to_city(building);
					空地数量 = city.max_devs - city.num_devs;
					base_score[i] += pk::max(5 + 空地数量, 20);
				}

				//因子4:小城市的状态和关隘状态修正
				if (i >= 建筑_城市末) base_score[i] /= 2;			//小城市减权

				if (ch::get_base_p(i).population < 10 * 10000 and base_statue[i] >= 据点_警戒) base_score[i] /= 3;	//关隘和过于贫瘠的小城市

				if (pk::get_building(i).facility == 设施_关隘 and base_statue[i] >= 据点_警戒)  //后方关隘没什么用
					base_score[i] /= 5;


					//增加常数项,以降低差距
				if (i >= 建筑_城市末) base_score[i] += 5;
				if (i < 建筑_城市末) base_score[i] += 10;


				if (i >= 建筑_城市末) base_score[i] = pk::max(base_score[i], 5);
				if (i < 建筑_城市末) base_score[i] = pk::max(base_score[i], 10);

				//对势力分赋值
				if (building.get_force_id() >= 0 and building.get_force_id() < 势力_末)
				{
					force_score[building.get_force_id()] += base_score[i];
				}

				//对势力分赋值
				if (building.get_district_id() >= 0 and building.get_district_id() < 军团_末)
				{
					district_score[building.get_district_id()] += base_score[i];
				}

				//*****************************************************计算城市留存兵力*****************************************************
				int weight = 0;
				int troops = 0;
				for (int j = 0; j < 据点_末; j++)
				{
					pk::building @src = pk::get_building(i);
					pk::building @dst = pk::get_building(j);
					int src_id = i;
					int dst_id = j;

					//此处顺序一定不能写错,指的是,邻居据点是否可以攻击此据点的意思
					if (ch::get_mid_base_id(dst_id, src_id).first == -1 and pk::get_building_distance(dst_id, src_id) == 2)
						continue;

					if (src_id != dst_id and (unit_distance[src_id][dst_id] < 6 or pk::get_building_distance(src_id, dst_id) == 1) and pk::is_enemy(src, dst))
						troops += base_max_effective_troops[dst_id] / 5; //近据点敌军

					if (src_id != dst_id and (unit_distance[src_id][dst_id] < 6 or pk::get_building_distance(src_id, dst_id) == 1) and src.get_force_id() == dst.get_force_id() and base_in_range_enemy_troops[j] == 0)
						troops -= base_max_effective_troops[dst_id] / 10; //近据点友军(友军可以帮忙降低留存兵力需求)

					//玩家据点在附近,尽量不去过分积极攻击
					if (src_id != dst_id and pk::get_building_distance(src_id, dst_id) == 1 and dst.is_player())
						troops += 10000;
				}
				troops = pk::min(troops, 30000);

				if (i >= 城市_末) troops = troops / 3;

				retained_troops[i] = troops + ((i >= 城市_末) ? 3000 : 5000);
				retained_troops[i] += base_around_enemy_troops[i];


				//******************************************************计算城市攻防能力*****************************************************
				int person_power = 0;
				int averge_power = 0;
				int troops_per_unit = 5000;
				int force_id = building.get_force_id();

				auto person_list = pk::get_person_list(building, pk::mibun_flags(身分_一般, 身分_都督, 身分_太守, 身分_君主));
				person_list.sort(function(a, b) {
					return (a.stat[武将能力_统率] * 3 + a.stat[武将能力_武力] + a.stat[武将能力_智力] > b.stat[武将能力_统率] * 3 + b.stat[武将能力_武力] + b.stat[武将能力_智力]); // 무장 정렬 (지력순)
				});

				//野战能力计算.
				//对于进攻方而言,进攻的战斗力实际上是可用兵力,可用武将,可用兵装的最小值
				//计算完可用兵力之后,再去计算可用武将,而不能用平均能力,这样会导致高属性的被忽略.
				pk::force @force;
				if (pk::is_valid_force_id(force_id))
				{
					@force = pk::get_force(building.get_force_id());
					if (pk::has_tech(force, 技巧_军制改革))
						troops_per_unit = 8000;
				}

				int field_effective_weapon1 = pk::get_weapon_amount(building, 1) + pk::get_weapon_amount(building, 2) + pk::get_weapon_amount(building, 3) + pk::get_weapon_amount(building, 4);
				int field_effective_weapon2 = pk::get_weapon_amount(building, 兵器_冲车) + pk::get_weapon_amount(building, 兵器_井阑) + pk::get_weapon_amount(building, 兵器_投石) + pk::get_weapon_amount(building, 兵器_木兽);
				int marchable_weapon = int(field_effective_weapon1 * 0.9 + field_effective_weapon2 * troops_per_unit) + pk::max(0, ai::marchable_troops[building.get_id()] - pk::get_troops(building));
				int field_effective_troops = pk::min(pk::get_troops(building), marchable_weapon, (person_list.count - 1) * troops_per_unit);
				int field_effective_person = field_effective_troops / 5000;

				if (pk::min(field_effective_person, int(person_list.count)) >= 1)
				{
					for (int k = 0; k < pk::min(field_effective_person, int(person_list.count)); k++)
					{
						pk::person @ilban = person_list[k];
						if (pk::is_unitize(ilban)) continue;

						person_power += (ilban.stat[武将能力_统率] * 3 + ilban.stat[武将能力_武力] + ilban.stat[武将能力_智力]) / 5;
					}
					averge_power = person_power / pk::min(field_effective_person, int(person_list.count));
				}

				base_atk_power[i] = averge_power * (field_effective_troops + base_around_self_troops[i]) / 10000;

				//守城能力计算
				//防守方可以分为守城兵力+县城兵力
				int def_troops = ch::city_spec_troops(building) + pk::max(building.troops - field_effective_troops, 0); //县城兵+剩余守城兵 
				base_def_power[i] = 50 * def_troops / 10000 + building.hp / 200; //城市攻防公式+城市攻击数值计算下来大约是50-60点,这里取50. 

				// if (pk::is_alive(force))
				// 	base_def_power[i] += ch::base_enemy_not_from_force(building, force); //目标城市范围内不属于己方的部队,实际上也会攻击己方,因此可以认为是防御部队(避免第三方势力过强,自己派人太少.)

				if (!pk::is_alive(force))
				{
					base_atk_power[i] = 0;
					base_def_power[i] = 0;
				}
			}

				//******************************************************计算城市合意武将*****************************************************
			for (int i = 0; i < 据点_末; i++)
			{
				pk::force @force = pk::get_force(pk::get_building(i).get_force_id());
				pk::district @district = pk::get_district(pk::get_building(i).get_district_id());
				if (force is null) continue;
				int force_person_count = pk::get_person_list(force, pk::mibun_flags(身份_君主, 身份_都督, 身份_太守, 身份_一般)).count;
				int district_person_count = pk::get_person_list(district, pk::mibun_flags(身份_君主, 身份_都督, 身份_太守, 身份_一般)).count;
				int total_base_count = ch::get_base_list(force).count;
				int total_city_count = pk::get_city_list(force).count;


				// 这个人数制约了小城非战斗状态下的,正常调度获得的人数上限.
				// 假如势力有10个人,1大城1小城,这时候基准需求则为2人.大城8人
				int k = 30;
				if (force_score[force.get_id()] > 0)
				{
					base_want_person[i] = int((1.0 * force_person_count * (base_score[i]) / (force_score[force.get_id()])));//向下取整,有利于减少低效移动,也保证了武将最小需要1人
					base_want_person[i] = pk::max(base_want_person[i], 1);

					//pk::trace(pk::format("{}所需武将_势力计算：{},势力武将：{},城市分：{},势力分：{},据点真实武将数量：{}", pk::decode(pk::get_name(pk::get_building(i))), base_want_person[i], force_person_count, base_score[i], force_score[force.get_id()], base_real_person[i]));
				}
				else
					base_want_person[i] = 0;


				if (district_score[district.get_id()] > 0 and district !is null and district.get_id() >= 0 and district.get_id() < 军团_末)
				{
					base_want_person_for_district[i] = int((1.0 * district_person_count * (base_score[i]) / (district_score[district.get_id()])));//向下取整,有利于减少低效移动,也保证了武将最小需要1人
					base_want_person[i] = pk::max(base_want_person[i], 1);

				//pk::trace(pk::format("{}所需武将_军团计算：{},军团武将：{},城市分：{},军团分：{},据点真实武将数量：{}", pk::decode(pk::get_name(pk::get_building(i))), base_want_person_for_district[i], district_person_count, base_score[i], district_score[district.get_id()], base_real_person[i]));
				}
				else
					base_want_person_for_district[i] = 0;

			}

			//******************************************************计算势力资源*****************************************************
			for (int i = 0; i < 据点_末; i++)
			{
				int force_id = pk::get_building(i).get_force_id();
				if (force_id >= 0 and force_id < 势力_末)
				{
					force_gold[force_id] += pk::get_gold(pk::get_building(i));
					force_food[force_id] += pk::get_food(pk::get_building(i));
					force_troops[force_id] += pk::get_troops(pk::get_building(i));
					force_troops_for_base[force_id] += pk::get_troops(pk::get_building(i));

					//pk::trace(pk::format("{},对应势力{},势力兵{},城市兵{},", pk::decode(pk::get_name(pk::get_building(i))), pk::decode(pk::get_name(pk::get_force(force_id))), ai::force_troops_for_base[force_id],pk::get_troops(pk::get_building(i))));

				}


				int district_id = pk::get_building(i).get_district_id();

				if (district_id >= 0 and district_id < 军团_末)
				{
					district_gold[district_id] += pk::get_gold(pk::get_building(i));
					district_food[district_id] += pk::get_food(pk::get_building(i));
					district_troops[district_id] += pk::get_troops(pk::get_building(i));
				}

			}
		}
		void calc_score_unit()
		{
			//************************************************************************************************************
			//------------------------------------------------部队循环赋值----------------------------------------------
			//************************************************************************************************************
			pk::list<pk::unit @> unit_list = pk::get_unit_list();
			for (int i = 0; i < unit_list.count; i++)
			{
				pk::unit @unit = unit_list[i];
				if (!pk::is_alive(unit))
					continue;

		//*****************************************计算势力资源*****************************************************
				int force_id = unit.get_force_id();
				force_gold[force_id] += unit.gold;
				force_food[force_id] += unit.food;
				force_troops[force_id] += unit.troops;



				//计算战斗部队的公共过滤器

				//  跳过非普通类型部队
				if (unit.type == 部队类型_运输)
					continue;

				if (unit.order == 部队任务_补给 or unit.order == 部队任务_待命 or unit.order == 部队任务_撤退)
					continue;

				int location_id = pk::get_building_id(unit.pos);
				pk::building @unit_location = pk::get_building(location_id);

		//*****************************************计算城市范围内作战兵力*****************************************************
				if (pk::is_enemy(unit, unit_location))
					base_in_range_enemy_troops[location_id] += unit.troops;

				if (pk::is_enemy(unit, unit_location) and unit.is_player())
					base_in_range_enemy_troops_from_player[location_id] += unit.troops;


		// *********************************计算特定势力正在攻击目标的兵力*****************************************

				auto scenario_ai_table_unit = pk::get_scenario().ai_table.unit[unit.get_id()];

				int unit_deploy_type = -1;
				int deploy_target = -1;

				//pk::trace(pk::format("{}部队长期任务类型{},长期任务目标:{}", pk::decode(pk::get_name(unit)), scenario_ai_table_unit.deploy_type, pk::decode(pk::get_name(pk::get_building(scenario_ai_table_unit.deploy_target)))));
				//pk::trace(pk::format("{}部队短期任务类型{},短期任务目标:{}", pk::decode(pk::get_name(unit)), unit.order, pk::decode(pk::get_name(pk::get_building(unit.target)))));

				if (int(scenario_ai_table_unit.force) == force_id)
				{
					unit_deploy_type = scenario_ai_table_unit.deploy_type;
					deploy_target = scenario_ai_table_unit.deploy_target;

				}


				//部队攻击对象为据点的时候,据点和部队不同势力,则把目标的城市认为是部队正在攻击的城市.
				if (unit.target_type == 部队任务对象_据点 and (unit.order == 部队任务_征服 or unit.order == 部队任务_攻城 or unit.order == 部队任务_攻击) and pk::is_valid_base_id(unit.target) and (pk::is_enemy(unit, pk::get_building(unit.target)) or pk::get_building(unit.target).get_force_id() == -1))
				{
					force_attack_base_troops[unit.get_force_id()][pk::get_building_id(pk::get_building(unit.target).pos)] += unit.troops;
					// pk::trace(pk::format("{}1所属城市:{},目标城市{}", pk::decode(pk::get_name(unit)), pk::get_person(unit.leader).service, pk::get_building_id(pk::get_building(unit.target).pos)));
					if (pk::get_person(unit.leader) !is null and pk::is_valid_base_id(pk::get_person(unit.leader).service))
					{
						base_attack_base_troops[pk::get_person(unit.leader).service][pk::get_building_id(pk::get_building(unit.target).pos)] += unit.troops;
					}

			   //pk::trace(pk::format("{}1兵力:{},目标城市{}:势力兵力{}", pk::decode(pk::get_name(unit)), unit.troops, pk::get_building_id(pk::get_building(unit.target).pos), force_attack_base_troops[unit.get_force_id()][pk::get_building_id(pk::get_building(unit.target).pos)]));
				}

				else if (int(scenario_ai_table_unit.force) == force_id and scenario_ai_table_unit.deploy_type == 部队出征类型_攻击 and pk::is_valid_base_id(scenario_ai_table_unit.deploy_target))
				{
					if (pk::is_enemy(unit, pk::get_building(scenario_ai_table_unit.deploy_target)) or pk::get_building(scenario_ai_table_unit.deploy_target).get_force_id() == -1)
					{
						//pk::trace(pk::format("{}1所属城市:{},目标城市{}", pk::decode(pk::get_name(unit)), pk::get_person(unit.leader).service, pk::get_building_id(pk::get_building(unit.target).pos)));

						force_attack_base_troops[unit.get_force_id()][scenario_ai_table_unit.deploy_target] += unit.troops;

						if (pk::get_person(unit.leader) !is null and pk::is_valid_base_id(pk::get_person(unit.leader).service))
						{
							//pk::trace(pk::format("{}1所属城市:{},目标城市{}", pk::decode(pk::get_name(unit)), pk::get_person(unit.leader).service, pk::get_building_id(pk::get_building(scenario_ai_table_unit.deploy_target).pos)));

							base_attack_base_troops[pk::get_person(unit.leader).service][pk::get_building_id(pk::get_building(scenario_ai_table_unit.deploy_target).pos)] += unit.troops;
						}
					}

				}


				else if (unit.target_type == 部队任务对象_部队 and pk::is_valid_unit_id(unit.target))
				{
					pk::unit @target_unit = pk::get_unit(unit.target);
					if (pk::is_valid_pos(target_unit.pos))
					{
						int target_unit_location_id = pk::get_building_id(target_unit.pos);
						pk::building @target_unit_location = pk::get_building(location_id);
						if (pk::is_enemy(unit, target_unit) and (pk::is_enemy(unit, target_unit_location) or target_unit_location.get_force_id() == -1))
						{
							force_attack_base_troops[unit.get_force_id()][target_unit_location_id] += unit.troops;
							if (pk::get_person(unit.leader) !is null and pk::is_valid_base_id(pk::get_person(unit.leader).service))
							{
								base_attack_base_troops[pk::get_person(unit.leader).service][target_unit_location_id] += unit.troops;
							}
						}
					}
				//pk::trace(pk::format("2{}兵力:{}:目标城市:{},势力兵力{}", pk::decode(pk::get_name(unit)), unit.troops, location_id, force_attack_base_troops[unit.get_force_id()][location_id]));
				}

				//踩在敌方领地内的部队,被认为是计算攻击目标的兵力
				else if (pk::is_enemy(unit, unit_location) or unit_location.get_force_id() == -1)
				{
					force_attack_base_troops[unit.get_force_id()][location_id] += unit.troops;
					if (pk::get_person(unit.leader) !is null and pk::is_valid_base_id(pk::get_person(unit.leader).service))
					{
						base_attack_base_troops[pk::get_person(unit.leader).service][location_id] += unit.troops;
					}
				//pk::trace(pk::format("{}3兵力:{}:势力兵力{}", pk::decode(pk::get_name(unit)), unit.troops, location_id, force_attack_base_troops[unit.get_force_id()][location_id]));

				}
			}



// *********************************计算正在攻击目标的兵力*****************************************

			pk::list<pk::unit @> unit_list_all = pk::get_unit_list();

			for (int i = 0; i < unit_list_all.count; i++)
			{
				pk::unit @unit = unit_list_all[i];
				if (!pk::is_alive(unit))
					continue;

				if (unit.attr.stat[部队能力_移动] == 0)
					pk::trace(pk::format("部队序号:{},{},兵种{},移动力.{}", i, pk::decode(pk::get_name(unit)), unit.weapon, unit.attr.stat[部队能力_移动]));				//  跳过非普通类型部队
				if (unit.type == 部队类型_运输)
					continue;

				if ((unit.order != 部队任务_征服 and unit.order != 部队任务_攻城 and unit.order != 部队任务_攻击) and unit.target_type != 部队任务对象_据点)
					continue;

				if ((unit.target_type != 部队任务对象_据点))
					continue;

				if (!pk::is_valid_base_id(unit.target) or unit.target >= 据点_末)
					continue;

				if (pk::is_enemy(unit, pk::get_building(unit.target)) or pk::get_building(unit.target).get_force_id() == -1)
				{
					base_attacked_troops[unit.target] += unit.troops;
	//pk::trace(pk::format("{}受到{}攻击,目前总的兵力为{}", pk::decode(pk::get_name(pk::get_building(unit.target))), unit.get_id(),base_attacked_troops[unit.target]));
			// 
				}

			}



			// for (int i = 0; i < 据点_末; i++)
			// {
			// 	if (!pk::is_valid_force_id(i)) continue;
			// 	for (int j = 0; j < 据点_末; j++)
			// 	{
			// 		base_attacking_troops[i] += base_attack_base_troops[i][j];
			// 		pk::trace(pk::format("{},{},为{}", pk::decode(pk::get_name(pk::get_building(i))), pk::decode(pk::get_name(pk::get_building(j))), base_attack_base_troops[i][j]));
			// 	}
			// }

			//检验相邻关系

			// for (int i = 0; i < 据点_末; i++)
			// {
			// 	for (int j = 0; j < 据点_末; j++)
			// 	{
			// 		pk::trace(pk::format("i:{},j:{}", i, j));
			// 		if (i != j)
			// 		pk::trace(pk::format("{},{},距离为{},是否可通行{}", pk::decode(pk::get_name(pk::get_building(i))), pk::decode(pk::get_name(pk::get_building(j))), pk::get_building_distance(i, j),ch::is_valid_routepath(i,j,pk::get_building(i).get_force_id())));
			// 	}
			// }
		}

		//---------------------------------------------------------------------------------------
		//          打印
		//---------------------------------------------------------------------------------------
		void print_score()
		{
			for (int i = 0; i < 据点_末; i++)
			{
				string base_name = pk::decode(pk::get_name(pk::get_building(i)));
				//pk::trace(pk::format("{} base_in_line_level {}", base_name, base_in_line_level[i]));
				// pk::trace(pk::format("{} marchable_troops {}", base_name, marchable_troops[i]));
				// pk::trace(pk::format("{} retained_troops {}", base_name, retained_troops[i]));
				// pk::trace(pk::format("{} base_around_self_troops {}", base_name, base_around_self_troops[i]));
				// pk::trace(pk::format("{} base_around_enemy_troops {}", base_name, base_around_enemy_troops[i]));
				// pk::trace(pk::format("{} base_in_range_enemy_troops {}", base_name, base_in_range_enemy_troops[i]));
				// pk::trace(pk::format("{} base_in_range_enemy_troops_from_player {}", base_name, base_in_range_enemy_troops_from_player[i]));
				// pk::trace(pk::format("{} base_max_effective_troops({}", base_name, base_max_effective_troops[i]));
				//  pk::trace(pk::format("{} base_atk_power {}", base_name, base_atk_power[i]));
				//  pk::trace(pk::format("{} base_def_power {}", base_name, base_def_power[i]));
				//pk::trace(pk::format("{}base_attacking_troops {}", base_name, base_attacking_troops[i]));
				//   pk::trace(pk::format("{} base_def_power {}", base_name, ch::base_enemy_not_from_force(pk::get_building(铃据点_南海), pk::get_force(1))));
				// pk::trace(pk::format("{} base_attacked_troops {}", base_name, base_attacked_troops[i]));
				//pk::trace(pk::format("{} base_score {}", base_name, base_score[i]));

			}

			for (int i = 0; i < 据点_末; i++)
			{
				if (!pk::is_valid_force_id(i)) continue;
				for (int j = 0; j < 据点_末; j++)
				{
					base_attacking_troops[i] += base_attack_base_troops[i][j];
					//pk::trace(pk::format("{},{},为{}", pk::decode(pk::get_name(pk::get_building(i))), pk::decode(pk::get_name(pk::get_building(j))), base_attack_base_troops[i][j]));
				}
			}

			// //
			// for (int i = 0; i < 非贼势力_末; i++)
			// {
			// 	if (!pk::is_valid_force_id(i)) continue;
			// 	for (int j = 0; j <  据点_末; j++)
			// 	{
			// 		pk::trace(pk::format("{},{},为{}", pk::decode(pk::get_name(pk::get_force(i))), pk::decode(pk::get_name(pk::get_building(j))), force_attack_base_troops[i][j]));
			// 	}
			// }

		}



	//---------------------------------------------------------------------------------------
	//          读取的时候计算一次据点
	//---------------------------------------------------------------------------------------
		void get_near_base()
		{
			//据点循环赋值

			for (int i = 0; i < 据点_末; i++)
			{
				pk::list<pk::building @> near_list;
				for (int neighbor_id = 0; neighbor_id < 据点_末; neighbor_id++)
				{
					if (neighbor_id == i)
						continue;
					int unitdistance = pk::get_building_distance(neighbor_id, i);

					//道路不通的情况下没办法.
					if (!ch::is_valid_routepath(i, neighbor_id, pk::get_building(i).get_force_id()))
						continue;

						//双方都是城市的时候,城市距离为1则认为相邻,否则不相邻.无论距离.
					if (i < 城市_末 and neighbor_id < 城市_末)
					{
						int city_distance = pk::get_city_distance(neighbor_id, i);
						if (city_distance == 1)
							near_list.add(pk::get_building(neighbor_id));
					}
					else
					{
						int building_distance = pk::get_building_distance(neighbor_id, i);

						if (unit_distance[i][neighbor_id] <= 2 or building_distance == 1)
						{
							near_list.add(pk::get_building(neighbor_id));
						}
					}


				}
				base_neibor_baselist[i] = near_list;
			}

			for (int i = 0; i < 据点_末; i++)
			{
				pk::list<pk::building @> near_list;
				for (int neighbor_id = 0; neighbor_id < 据点_末; neighbor_id++)
				{
					if (neighbor_id == i)
						continue;
					int unitdistance = pk::get_building_distance(neighbor_id, i);

					//道路不通的情况下没办法.
					if (!ch::is_valid_routepath(i, neighbor_id, pk::get_building(i).get_force_id()))
						continue;

						//双方都是城市的时候,城市距离为1则认为相邻,否则不相邻.无论距离.
					if (i < 城市_末 and neighbor_id < 城市_末)
					{
						int city_distance = pk::get_city_distance(neighbor_id, i);
						if (city_distance == 1)
							near_list.add(pk::get_building(neighbor_id));
					}
					else
					{
						int building_distance = pk::get_building_distance(neighbor_id, i);


					//只要路通,12以内都可以去
						if (unit_distance[i][neighbor_id] <= 10)
						{
							near_list.add(pk::get_building(neighbor_id));
						}
					}


				}
				base_near_baselist[i] = near_list;
			}

			//计算层级
			for (int i = 0; i < 据点_末; i++)
			{
				pk::list<pk::building @> near_list;
				int min_level = 999;
				for (int neighbor_id = 0; neighbor_id < 据点_末; neighbor_id++)
				{

					if (neighbor_id == i)
						continue;
					if (pk::get_building(i).get_force_id() == pk::get_building(neighbor_id).get_force_id())
						continue;
					int building_distance = pk::get_building_distance(neighbor_id, i);

					if (pk::get_building(i).get_force_id() != pk::get_building(neighbor_id).get_force_id() and min_level > building_distance)
						min_level = building_distance;
					string base_name = pk::decode(pk::get_name(pk::get_building(i)));
					//pk::trace(pk::format("{} ,{}距离 {}", pk::decode(pk::get_name(pk::get_building(i))), pk::decode(pk::get_name(pk::get_building(neighbor_id))), building_distance));

				}
				base_in_line_level[i] = min_level;
			}

						//据点循环赋值
			for (int i = 0; i < 据点_末; i++)
			{
				pk::list<pk::building @> near_list;
				for (int neighbor_id = 0; neighbor_id < 据点_末; neighbor_id++)
				{
					if (neighbor_id == i)
						continue;
					// 	//pk::trace(pk::format("{},{},据点距离为{}", pk::decode(pk::get_name(pk::get_building(i))), pk::decode(pk::get_name(pk::get_building(neighbor_id))),pk::get_building_distance(neighbor_id, i) ));


					int force_id_src = pk::get_building(i).get_force_id();
					int force_id_dst = pk::get_building(neighbor_id).get_force_id();
					if (force_id_src >= 非贼势力_末 or force_id_dst >= 非贼势力_末) continue;
					if (force_id_src < 0 or force_id_dst < 0) continue;

					if (pk::get_building_distance(neighbor_id, i) == 1 and force_id_src != force_id_dst)
					{
						force_to_force_enemy_base[force_id_src][force_id_dst]++;
						//force_to_force_enemy_base[force_id_dst][force_id_src]++;
						//pk::trace(pk::format("{},{},势力ID{},{},相邻的敌方据点数量为{},{}", pk::decode(pk::get_name(pk::get_building(i))), pk::decode(pk::get_name(pk::get_building(neighbor_id))), i, neighbor_id, force_to_force_enemy_base[force_id_src][force_id_dst], force_to_force_enemy_base[force_id_dst][force_id_src]));

					}
				}
			}


			//检验敌对关系
			// for (int i = 0; i < 非贼势力_末; i++)
			// {
			// 	if (!pk::is_valid_force_id(i)) continue;
			// 	for (int j = 0; j < 非贼势力_末; j++)
			// 	{
			// 		if (!pk::is_valid_force_id(j)) continue;
			// 		if (i == j)  continue;
			// 		if (force_to_force_enemy_base[i][j] > 1)
			// 			force_to_force_enemy_base[i][j] /= 2;
			// 			//pk::trace(pk::format("{},{},势力ID{},{},相邻的敌方据点数量为{}", pk::decode(pk::get_name(pk::get_force(i))), pk::decode(pk::get_name(pk::get_force(j))), i, j, force_to_force_enemy_base[i][j]));
			// 	}
			// }
		}
	}
	Main main;

}